﻿<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
<html>
<head>
<title>Упаковщики - ЗА и ПРОТИВ</title>
<meta http-equiv="Content-Type" Content="text/html; charset=utf-8">
<link rel="stylesheet" type="text/css" href="../../styles/styles.css">
<script language="javascript" src='../links.js' type="text/javascript"></script>
</head>

<body>

<a name="top"></a>
<h1>Упаковщики - ЗА и ПРОТИВ</h1>
<div class=navbar>
<a href="../index.html">главная</a> |
<a href="index.html">статьи</a>
</div>

<div align=right><code>
Jordan Russell<br>
</code></div>
<hr color="#003399">

<p class=plain>Многие посетители моей страницы часто спрашивают следующее:</p>
<div class=idea>"Если я хочу уменьшить размер своей программы, то почему бы ни
использовать EXE компрессор? Это позволит сделать размер EXE значительно
меньше, чем использование StripReloc! Почему вы против этого"</div>

<p class=plain>Многие не понимают (или просто не знают), что при использовании
Компрессоров типа <a href="http://www.asprotect.ru/aspack.html">ASPack</a>
и <a href="https://github.com/upx/upx">UPX</a> они многое теряют. По моему мнению
EXE компрессоры это не то, что следует применять бездумно. Позвольте
разъяснить.</p>

<p class=plain>В DOS, когда вы запускаете программу, весь её код загружается с диска
В оперативную память и остаётся в ней до конца. Если не хватает памяти
для загрузки всей программы, то вы получите сообщение об ошибке
"out of memory".</p>

<p class=plain>Современные многозадачные Операционные Системы (ОС), такие как
Windows 95/98 и NT используют метод названный "Виртуальная память"
(virtual memory). Когда программа загружается, то в память сразу не грузится весь код,
как в случае DOS программ. Вместо этого загружается только часть кода,
которая требуется для исполнения. Например, ваша программа имеет
пункт меню "Print" и код назначенный, который исполняется при выборе
этого пункта. Этот код загружается в память только когда пользователь
выбирает данный пункт. И если после загрузки кода в память он не используется некоторое время,
то код выгружается из памяти, память освобождается и может быть
использована другими программами. Данный процесс называется "paging" и
полностью прозрачно для программы.</p>

<p class=plain>Другой путь экономии использования памяти - это использование одной и той
же области памяти для нескольких экземпляров программы (или DLL).
Другими словами, нет реальной разницы между одним экземпляром программы
или сотней экземпляров программы в количестве используемой физической
памяти выделенной для кода.</p>

<p class=plain>Если бы Win32 вели бы себя как DOS программы,
то есть загрузка всего кода в память и оставались бы там до завершения и
также бы не разделяли память для разных экземпляров программы, вы бы
быстро исчерпали всю доступную память.</p>

<p class=plain>Вот именно это и делают текущие Win32 EXE компрессоры!
Они полностью блокирую работу метода "paging" разжимая весь код в память и
сохраняя его там до конца работы программы.
И поскольку код в упакованном EXE файле хранится не в обычном "raw" формате
(то есть в том виде какой он в памяти), то ОС не в состоянии разделять
тот же блок памяти для нескольких экземпляров программы.
Многие используют EXE компрессоры как сильное оружие для уменьшения потерь
под размер на диске, но я хочу спросить:
<b>Что более накладно - мегабайты на диске или мегабайты оперативной памяти?
Действительно ли стоит увеличивать требования вашей программы на оперативную
память за счёт сохранения несколько килобайт дискового пространства?</b></p>

<h3>Тест</h3>
<p class=plain>Я слышал, что многие сжимаю свои EXE из MS Office, поэтому я решил
провести тест по реальному использованию памяти именно на MSACCESS.EXE.
Я сжал MSACCESS.EXE из Office 2000 с помощью UPX и сравнил использование
памяти с помощью NT 4.0's Task Manager...<br>
Ниже приведены (удивительные) результаты теста.</p>

<table border=1 widtd=80%>
<tr><td>&nbsp;</td>
<td><b>File Size&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</td>
<td><b>Process "Mem Usage"&nbsp;&nbsp;</b><br>1 instance</td>
<td><b>"Commit Charge Total"</b>&nbsp;&nbsp;<br>1 instance difference</td>
<td><b>"Commit Charge Total"</b>&nbsp;&nbsp;<br>20 instances difference</td>
</tr>
<tr bgcolor="#c0c0c0">
<td><b>uncompressed</b>&nbsp;&nbsp;</td>
<td>4,677,686</td>
<td>2580 KB</td>
<td>1084 KB</td>
<td>25396 KB</td>
</tr>
<tr bgcolor="#c0c0c0">
<td><b>UPX 0.82</b>&nbsp;&nbsp;</td>
<td>2,436,096</td>
<td>6852 KB</td>
<td>6192 KB</td>
<td>126968 KB</td>
</tr></table>

<p class=plain>Опираясь на 1 экземпляр результаты показанные выше, показываю что:
сжатый MSACCESS.EXE забирает на 5MB больше памяти. Ну не так уж плохо,
но уже ощутимо.

<p class=plain>Но вот уже для 20 экземпляров результат следующий.
Да вы читаете правильно. Это не типографская ошибка!!!
Для 20 экземпляров сжатого MSACCESS.EXE требуют на 100 Мб больше,
чем не сжатый.

<p class=plain>Мой тест был сделан на машине с 256MB оперативной памяти, желаю удачи
при проведении теста на машине с 64 Мб память.
Для запуска 20 экземпляров MSACCESS.EXE я использовал 20 строчный bat файл,
каждая строка которого содержала следующий тест: "START MSACCESS.EXE".
Плохая весть: запуск 20 экземпляров MSACCESS.EXE  немного больше времени
(4 секунды против 1.5), которое я отношу на счёт взаимного использования
кода между экземплярами и времени требуемым на распаковку программы.
Это показывает, что малый размер файла не гарантирует более быструю
загрузку.

<p class=plain>Поскольку я делал фокус на тестирования кода, я использовал следующие ключи
для UPX: <code>--compress-exports=0 --compress-icons=0 --compress-resources=0</code>.
Я планировал протестировать и ASPack, но запустить сжатый MSACCESS.EXE не
удалось. Но я думаю, что результат был бы сравним с UPX, также я не
пробовал тестировать другие упаковщики.

<h3>Заключение</h3>
<p class=plain>Цель данной статьи не является принизить авторов EXE компрессоров, а только
отражает факты, о которых они предпочитают умалчивать.
Да EXE компрессоры могут быть хорошим выбором когда нужно. Но в то же время
много причин не получения нужного результата, как это показывает мой тест.


<h3>Дополнение от 20 апреля 2000</h3>
<ol>
<li>Другой недостаток использования EXE компрессоров, не отмеченный выше,
это то что многие старые сканеры вирусов считаю, что в эти упакованные
файлы заражены вирусом, (некоторые из них докладывают "неизвестный вирус",
некоторые "Win32.BackDoor"). Это было основной причиной для отказа
использования в моём инсталляторе "Inno Setup", а не по причине
расточительного использования памяти. Я был очень огорчён ругательными
письмами, которые я стал получать по поводу распространения вирусов.
Я даже был обозван лжецом, когда пытался объяснить это. Пришлось даже
увидеть предупреждение на некоторых сайтах, о том, что "Inno Setup"
может содержать вирус. Как результат, использование EXE компрессоров
может привести к потере бизнеса или подрыву репутации.

<li>Я конечно не думаю, что кто то будет запускать 20 экземпляров
MS Access одновременно. Это было сделано с целью иллюстрации, что затраты
на память возрастаю экспоненциально при запуске нескольких экземпляров.
В большинстве случаев не запускают нескольких экземпляров программ,
но DLL часто загружаются и используются одновременно несколькими
программами.
Взаимное использование кода относится и к DLL также, о чём я забыл упомянуть
в статье.

<li>Многие люди спрашивают, "а как насчёт Shrinker?" Blink, Inc. преподносит,
что Shrinker "единственный продукт, который распаковывает EXE блоками
по требованию (ON DEMAND), а не при запуске программы", и это объясняет
почему распаковщик занимает примерно 30 килобайт для каждой программы.
Мои начальные тесты со Shrinker были неполными и проведу дополнительное
тестирование Shrinker в будущем.
</ol>

<hr>
<p>
Примечание переводчика:<br>
Джордан Рассел (Jordan Russell) автор программ и компонент
Inno Setup, StripReloc, ToolBar97, ToolBar 2000<br>
Оригинал находится <a href="https://jrsoftware.org/striprlc.php#execomp">https://jrsoftware.org/striprlc.php#execomp</a>

<p>Перевод:
Анатолий Подгорецкий<br>
<a href="mailto:Anatoly Podgoretsky <nps@vnet.ee>?subject=Packers">anatoly@podgoretsky.com</a><br>
<a href="https://web.archive.org/web/20030216114519/http://www.nps.vnet.ee/">http://nps.vnet.ee (archive.org)</a>
</p>

<div align=right><code>
<br>&nbsp;<br>
21.04.2000
</code></div>

См. также статью Криса Касперски "Паковать или не паковать?"<br>
<small><a href="https://web.archive.org/web/20031203011755/http://www.programme.ru:80/archive/2001/10/102001_1.phtml">http://www.programme.ru:80/archive/2001/10/102001_1.phtml (archive.org)</a></small><br><br>

<div class=seecont><a href="#top">наверх</a></div>

</body>
</html>
